Spring Cloud-使用config类配置tomcat

1.起因

    公司开发一个系统,采用的是Spring Cloud开发。在项目部署时需要在一台机器启动多个相同的服务,为了避免修改配置文件,使用config来配置tomcat。结果导致了注册到eureka的服务错误,在使用feign进行调用时出现错误。

2.TomcatConfig

    使用Java配置类配置tomcat。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
package com.jlb.common.util.aop.tomcat;

import java.io.IOException;
import java.net.ServerSocket;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.AutoConfigureBefore;
import org.springframework.boot.autoconfigure.web.EmbeddedServletContainerAutoConfiguration;
import org.springframework.boot.bind.RelaxedPropertyResolver;
import org.springframework.boot.context.embedded.EmbeddedServletContainer;
import org.springframework.boot.context.embedded.tomcat.TomcatEmbeddedServletContainerFactory;
import org.springframework.boot.web.servlet.ServletContextInitializer;
import org.springframework.cloud.netflix.eureka.EurekaClientAutoConfiguration;
import org.springframework.context.EnvironmentAware;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.env.Environment;
import org.springframework.core.env.PropertyResolver;

@Configuration
@AutoConfigureBefore({EmbeddedServletContainerAutoConfiguration.class,EurekaClientAutoConfiguration.class})
public class TomcatConfig extends TomcatEmbeddedServletContainerFactory implements EnvironmentAware{
@Value("${server.port:10000}")
public static int port;

@Override
public EmbeddedServletContainer getEmbeddedServletContainer(ServletContextInitializer... initializers){
int maxPort = port/10*10+10;
if(port >= 10000) {
while (port < 65535) {
try {
ServerSocket socket = new ServerSocket(port);
socket.close();
break;
} catch (IOException e) {
port ++ ;
}
}
}else {
for(int i = 0 ; i < 10 && port < maxPort ; i ++) {
try {
ServerSocket socket = new ServerSocket(port + i);
port = port + i;
socket.close();
break;
} catch (IOException e) {
continue;
}
}
}
this.setPort(port);
return super.getEmbeddedServletContainer(initializers);
}

@Override
public void setEnvironment(Environment environment) {
PropertyResolver resolver = new RelaxedPropertyResolver(environment, "server.");
String port = resolver.getProperty("port", "10000");
TomcatConfig.port = Integer.valueOf(port);
}

}

3.手动修改注册到eureka的信息

    在经过2的tomcat配置后,会导致注册到eureka的信息错误,需要手动修改注册信息。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
package com.jlb.common.util.aop.tomcat;

import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
import org.springframework.boot.autoconfigure.AutoConfigureBefore;
import org.springframework.cloud.commons.util.InetUtils;
import org.springframework.cloud.netflix.eureka.EurekaClientAutoConfiguration;
import org.springframework.cloud.netflix.eureka.EurekaInstanceConfigBean;
import org.springframework.context.annotation.Configuration;

@Configuration
@AutoConfigureAfter({TomcatConfig.class})
@AutoConfigureBefore({EurekaClientAutoConfiguration.class})
public class EurekaInstanceConfig extends EurekaInstanceConfigBean implements InitializingBean{
@Value("${server.context-path:}")
private String contextPath;

public EurekaInstanceConfig(InetUtils inetUtils) {
super(inetUtils);
}
@Override
public void afterPropertiesSet() throws Exception {
String address = getIpAddress();
setInstanceId(address + ":" + TomcatConfig.port);
setStatusPageUrl("http://"+address+":"+TomcatConfig.port+contextPath+"/swagger-ui.html");
setHomePageUrl("http://"+address+":"+TomcatConfig.port+"/");
setHealthCheckUrl("http://"+address+":"+TomcatConfig.port+contextPath+"/health");
setNonSecurePort(TomcatConfig.port);
}
}